
#include "xfat.h"
#include "xdisk.h"

extern u8_t temp_buffer[512];           //缓存优化

/**
 * @brief 从dbr中解析出fat相关配置参数
 * 
 * @param xfat xfat结构
 * @param dbr 读取的设备dbr
 * @return xfat_err_t 
 */
static xfat_err_t parse_fat_header (xfat_t * xfat, dbr_t * dbr)
{
    xdisk_part_t *xdisk_part = xfat->disk_part;

    //解析DBR参数，解析出有用参数(字节大小)
    xfat->fat_tbl_sectors = dbr->fat32.BPB_FATSz32;

    //如果禁止FAT镜像，只刷新一个FAT表
    //disk_part->start_block为该分区的绝对物理扇区号，所以不需要再加上Hidden_sector
    if(dbr->fat32.BPB_ExtFlags & (1 << 7))
    {
        u32_t table = dbr->fat32.BPB_ExtFlags & 0xf;
        xfat->fat_start_sector = dbr->bpb.BPB_RsvdSecCnt + xdisk_part->start_sector + table * xfat->fat_tbl_sectors;
        xfat->fat_tbl_nr = 1;
    }
    else
    {
        xfat->fat_start_sector = dbr->bpb.BPB_RsvdSecCnt + xdisk_part->start_sector;
        xfat->fat_tbl_nr = dbr->bpb.BPB_NumFATs;
    }

    xfat->total_sectors = dbr->bpb.BPB_TotSec32;

    return FS_ERR_OK;
}


/**
 * @brief 初始化FAT项
 * 
 * @param xfat xfat结构
 * @param xdisk_part 分区结构
 * @return xfat_err_t 
 */
xfat_err_t xfat_open(xfat_t * xfat, xdisk_part_t * xdisk_part)
{
    dbr_t *dbr = (dbr_t *)temp_buffer;
    xdisk_t *xdisk = xdisk_part->disk;
    xfat_err_t err;

    xfat->disk_part = xdisk_part;

    //读取dbr参数区
    err = xdisk_read_sector(xdisk,(u8_t *)dbr,xdisk_part->start_sector,1);
    if(err < 0)
    {
        return err;
    }

    //解析dbr参数中的fat相关信息
    err = parse_fat_header(xfat,dbr);
    if(err < 0)
    {
        return err;
    }

    return FS_ERR_OK;
}
